#include "Scripting.hpp"

namespace zen {

	namespace sys {

		
		bool Scripting::initialized = false;
		std::map<std::string, std::string> Scripting::scriptFiles;
		lua_State* Scripting::luaState;


		bool Scripting::initialize() {
			luaState = luaL_newstate();
			luaL_openlibs(luaState);

			std::string scriptsConfigResource = zen::sys::Settings::get("paths.scripts") + zen::sys::Settings::get("resources.scriptsConfig");
			jsl::Node* scriptsConfig = zen::sys::Resources::load(scriptsConfigResource);
			if (scriptsConfig == NULL) {
				return false;
			}

			jsl::Node* scriptsArray = scriptsConfig->at("scripts");
			if (scriptsArray != NULL)
				for (unsigned int i = 0; i < scriptsArray->size(); i++) {
					jsl::Node* scriptNode = scriptsArray->at(i);
					scriptFiles.insert(std::pair<std::string, std::string>(scriptNode->at("id")->value(), scriptNode->at("file")->value()));
				}
			jsl::Node* defaultLoadScripts = scriptsConfig->at("defaultLoad");
			if (defaultLoadScripts != NULL)
				for (unsigned int i = 0; i < defaultLoadScripts->size(); i++) {
					std::map<std::string, std::string>::iterator iter = scriptFiles.find(defaultLoadScripts->at(i)->value());
					if (iter != scriptFiles.end()) {
						luaL_dofile(luaState, (zen::sys::Settings::get("paths.scripts") + iter->second).c_str());
					}
				}

			delete scriptsConfig;
			initialized = true;
			return true;
		}

		void Scripting::call(const std::string& functionName, Event* event) {
			lua_getglobal(luaState, functionName.c_str());
			event->pushState(luaState);
			lua_call(luaState, 2, 1);
			lua_pop(luaState, 1);
		}

		bool Scripting::loadModule(const std::string& moduleName) {
			std::map<std::string, std::string>::iterator iter = scriptFiles.find(moduleName);
			if (iter == scriptFiles.end())
				return false;
			luaL_dofile(luaState, iter->second.c_str());
			return true;
		}


	} // namepace sys

} // namepace zen
